summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorChristian Kamm <christian.d.kamm@nokia.com>2010-03-23 14:06:01 +0100
committerChristian Kamm <christian.d.kamm@nokia.com>2010-03-26 13:05:03 +0100
commitd91f0eb67e2226d118af4874e069dac59652bd2a (patch)
tree949c6c261d8ae836eaa248662f04d41334a31d38
parent80d39f61c92d81fc8408c5d3a9b67f2b2f9d082a (diff)
Store the root coroutine in its own QThreadStorage to guarantee deletion.
Previously, each thread that used coroutines leaked the root coroutine on exit.
-rw-r--r--src/coroutine.cpp7
1 files changed, 7 insertions, 0 deletions
diff --git a/src/coroutine.cpp b/src/coroutine.cpp
index 27050d1..632b953 100644
--- a/src/coroutine.cpp
+++ b/src/coroutine.cpp
@@ -141,6 +141,9 @@ void Coroutine::setStack(void *memory, int size)
initializeStack(memory, size, &entryPoint, &_stackPointer);
}
+// owns the per-thread root coroutine, required to assure deletion on thread exit
+static QThreadStorage<Coroutine *> qt_threadRootCoroutine;
+// points to the currently running coroutine
static QThreadStorage<Coroutine **> qt_currentCoroutine;
/*!
@@ -153,9 +156,13 @@ Coroutine *Coroutine::currentCoroutine()
{
// establish a context for the starting coroutine
if (!qt_currentCoroutine.hasLocalData()) {
+ // set qt_currentCoroutine before actually constructing the root
+ // coroutine to avoid recursing through the constructor call below
Coroutine **currentPtr = new Coroutine*;
qt_currentCoroutine.setLocalData(currentPtr);
+
*currentPtr = new Coroutine;
+ qt_threadRootCoroutine.setLocalData(*currentPtr);
(*currentPtr)->_status = Running;
return *currentPtr;
}